<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>class继承</title>
  </head>
  <body>
    <h3>class继承</h3>
    <h4>由于要打印原型对象，在浏览器操作比较方便，就用了html文件。</h4>
    <script>
      class Parent {
        constructor(name) {
          // 公共属性，可以通过 .操作符修改
          this._name = name;
          // 放在了实例上
          this.sayName1 = function () {
            console.log(`我的名字1是：${this._name}`);
          };
        }

        // 公共方法-放在原型链上
        sayName() {
          console.log(`父类的，名字是：${this._name}`);
        }

        get name() {
          return this._name;
        }

        // 当然类中内部修改也是可以的
        set name(name) {
          this._name = name;
        }

        // 静态方法，一般用于比较2个实例，这里比较谁的名字长
        static compareName(a, b) {
          console.log(`${a.name}, 名字长度为${a.name.length}`);
          console.log(`${b.name}, 名字长度为${b.name.length}`);
          console.log(
            (a.name.length > b.name.length ? a.name : b.name) + "  的名字长"
          );
          return a.name.length > b.name.length;
        }
      }

      console.log("=========父类=========");
      let p = new Parent("Penk");
      p.sayName();
      p.name = "Penk是个码农";
      p.sayName();

      class Children extends Parent {
        // 私有变量
        // 1. 构造函数
        // 2. 内部方法或者get、set读取器
        #job = "没工作";
        // 构造函数
        constructor(name, job) {
          super(name);
          this.#job = job;
        }

        // 公共方法-放在原型链上 -- 父类有，这边重写
        sayName() {
          // 访问父类的方法。
          super.sayName();
          console.log(`子类的，名字是：${this._name}`);
        }

        // 内部方法
        sayJob() {
          console.log(`我叫${this.name}，我的工作是：${this.#job}`);
        }

        // 读取器
        get job() {
          return this.#job;
        }

        set job(j) {
          this.#job = j;
        }
      }

      console.log("=========子类=========");
      let person = new Children("钟先生", "程序员");
      person.sayName();
      person.name = "钟先生超级帅";
      person.sayName();
      // 直接修改，因为是公共属性
      person._name = "钟先生";
      person.sayName();

      person.sayJob();
      person.job = "扫地大叔1111111";
      person.sayJob();
      // 无效，根本读不到该值...
      person["#job"] = "程序员";
      person.sayJob();

      // 静态方法比较长度
      let person2 = new Children("刘备", "主公");
      Parent.compareName(person, person2);

      console.log(p);
      console.log(person);
      console.log(person2);
    </script>
  </body>
</html>
